package com.team.cloudsharing.dao.sharefolder;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import org.apache.log4j.Logger;
import org.hibernate.Criteria;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.criterion.Restrictions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import com.team.cloudsharing.dao.folder.FolderDO;
import com.team.cloudsharing.dao.user.UserDO;
import com.team.cloudsharing.ultis.CastArrayList;

@Repository
public class ShareFolderDAOImpl implements ShareFolderDAO{
	
	final static Logger logger = Logger.getLogger(ShareFolderDAOImpl.class);

	@Autowired
	SessionFactory sessionFactory;
	
	@Override
	public long insertShareFolder(ShareFolderDO shareFolderDO) {
		long sharedFolderId = -1;
		Session session = null;
		if (shareFolderDO != null) {
			try {
				session = sessionFactory.openSession();
				Transaction tx = session.beginTransaction();
				session.saveOrUpdate(shareFolderDO);
				tx.commit();
				Serializable id = session.getIdentifier(shareFolderDO);
				sharedFolderId = (Long) id;
			} catch (Exception e) {
				logger.error(e.getMessage());
			} finally {
				try {
					session.close();
				} catch (Exception e2) {
					logger.error(e2.getMessage());
				}
			}
		}
		return sharedFolderId;
	}
	
	@Override
	public long updateShareFolder(ShareFolderDO shareFolderDO) {
		return insertShareFolder(shareFolderDO);
	}

	@Override
	public ShareFolderDO findShareFolderByFolderNameAndUserId(String userFolderName, UserDO userDO){
		ShareFolderDO shareFolderDO = null;
		Session session = null;
		try {
			session = sessionFactory.openSession();
			session.beginTransaction();
			Criteria criteria = session.createCriteria(ShareFolderDO.class);
			criteria.add(Restrictions.eq("userFolderName", userFolderName));
			criteria.add(Restrictions.eq("userDO", userDO));
			shareFolderDO = (ShareFolderDO) criteria.uniqueResult();
		} catch (Exception e) {
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
		return shareFolderDO;
	}

	@Override
	public List<ShareFolderDO> findAllShareFolderByUserId(UserDO userDO) {
		List<ShareFolderDO> listShareFolderDOs = new ArrayList<ShareFolderDO>();
		Session session = null;
		try {
			session = sessionFactory.openSession();
			session.beginTransaction();
			Criteria criteria = session.createCriteria(ShareFolderDO.class);
			criteria.add(Restrictions.eq("userDO", userDO));
			listShareFolderDOs = CastArrayList.castCollection(criteria.list(), ShareFolderDO.class);
		} catch (Exception e) {
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
		return listShareFolderDOs;
	}

	@Override
	public boolean deleteShareFolder(long shareFolderId){
		boolean statusDelete = false;
		Session session = null;
		try {
			session = sessionFactory.openSession();
			ShareFolderDO shareFolderDO = (ShareFolderDO) session.load(ShareFolderDO.class, shareFolderId);
			Transaction tx = session.getTransaction();
			session.beginTransaction();
			session.delete(shareFolderDO);
			tx.commit();
			statusDelete = true;
		} catch (Exception e) {
			statusDelete = false;
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
		return statusDelete;
	}

	@Override
	public List<ShareFolderDO> findAllShareFolderByFolderDO(FolderDO folderDO) {
		List<ShareFolderDO> listShareFolderDOs = new ArrayList<ShareFolderDO>();
		Session session = null;
		try {
			session = sessionFactory.openSession();
			session.beginTransaction();
			Criteria criteria = session.createCriteria(ShareFolderDO.class);
			criteria.add(Restrictions.eq("folderDO", folderDO));
			listShareFolderDOs = CastArrayList.castCollection(criteria.list(), ShareFolderDO.class);
		} catch (Exception e) {
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
		return listShareFolderDOs;
	}

	@Override
	public void deleteShareFolderByFolderDOAndUserDO(FolderDO folderDO, UserDO userDO) {
		Session session = null;
		String hql = "DELETE FROM share_folder WHERE folder_id = :folderId AND user_id = :userId";
		try {
			session = sessionFactory.openSession();
			Query query = session.createSQLQuery(hql);
			query.setParameter("folderId", folderDO.getFolderId());
			query.setParameter("userId", userDO.getUserId());
			session.beginTransaction();
			query.executeUpdate();
			session.getTransaction().commit();
		} catch (Exception e) {
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
	}

	@Override
	public void deleteShareFolderByFolderDO(FolderDO folderDO) {
		Session session = null;
		String hql = "DELETE FROM share_folder WHERE folder_id = :folderId";
		try {
			session = sessionFactory.openSession();
			Query query = session.createSQLQuery(hql);
			query.setParameter("folderId", folderDO.getFolderId());
			session.beginTransaction();
			query.executeUpdate();
			session.getTransaction().commit();
		} catch (Exception e) {
			logger.error(e.getMessage());
		} finally {
			try {
				session.close();
			} catch (Exception e2) {
				logger.error(e2.getMessage());
			}
		}
	}

	@Override
    public ShareFolderDO findShareFolderByFolderIdAndUserId(FolderDO folderDO, UserDO userDO){
            ShareFolderDO shareFolderDO = null;
            Session session = null;
            try {
                    session = sessionFactory.openSession();
                    session.beginTransaction();
                    Criteria criteria = session.createCriteria(ShareFolderDO.class);
                    criteria.add(Restrictions.eq("folderDO", folderDO));
                    criteria.add(Restrictions.eq("userDO", userDO));
                    shareFolderDO = (ShareFolderDO) criteria.uniqueResult();
            } catch (Exception e) {
                    logger.error(e.getMessage());
            } finally {
                    try {
                            session.close();
                    } catch (Exception e2) {
                            logger.error(e2.getMessage());
                    }
            }
            return shareFolderDO;
    }

}
